package gateway.mgt.api.ratelimit

import com.amihaiemil.camel.Yaml
import com.amihaiemil.camel.YamlSequenceBuilder
import gateway.mgt.api.ApiDefinition

@groovy.transform.ToString(includePackage = false, includes = ["name", "apiLimit", "userLimit"])
class RateLimitStrategy implements ApiDefinition.Pluggable {

    String name

    Long apiLimit
//    Long appLimit
    Long userLimit

    String description

    Date dateCreated
    Date lastUpdated

    static hasMany = [apiDefinitions: ApiDefinition, specialUsers: SpecialUser]

    static constraints = {
        name(blank: false)
        apiLimit(nullable: false, min: 0L)
        userLimit(nullable: true, min: 0L, validator: { val, obj -> !val || val <= obj.apiLimit })
//        appLimit(nullable: true, min: 0L, validator: { val, obj -> !val || val <= obj.userLimit })
        specialUsers()
        description(nullable: true, maxSize: 200, widget: 'textarea')
        dateCreated()
        lastUpdated()
    }

    @Override
    void plug(Map<String, YamlSequenceBuilder> routeBuildElements, final ApiDefinition current) {
        if (specialUsers)
            routeBuildElements.filters = routeBuildElements.filters.add("AddRequestHeader=SpecialUsers,${specialUsers.collect { it.clientId }.join(';')}")

        routeBuildElements.filters = routeBuildElements.filters.add(
                Yaml.createYamlMappingBuilder().add("name", "RequestRateLimiter").add("args",
                        Yaml.createYamlMappingBuilder()
                                .add("key-resolver", specialUsers ? "\"#{@remoteAddressKeyResolver4Whitelist}\"" : "\"#{@remoteAddressKeyResolver}\"")
                                .add("redis-rate-limiter.replenishRate", apiLimit as String)
                                .add("redis-rate-limiter.burstCapacity", apiLimit as String)
                                .build()
                ).build())

        if (userLimit) {
            routeBuildElements.filters = routeBuildElements.filters.add(
                    Yaml.createYamlMappingBuilder().add("name", "RequestRateLimiter").add("args",
                            Yaml.createYamlMappingBuilder()
                                    .add("key-resolver", specialUsers ? "\"#{@principalNameKeyResolver4Whitelist}\"" : "\"#{@principalNameKeyResolver}\"")
                                    .add("redis-rate-limiter.replenishRate", userLimit as String)
                                    .add("redis-rate-limiter.burstCapacity", userLimit as String)
                                    .build())
                            .build())
        }

        if (specialUsers) {
            specialUsers.each { specialUser -> specialUser.plug(routeBuildElements, current) }
            routeBuildElements.filters = routeBuildElements.filters.add("RemoveRequestHeader=SpecialUsers")
        }
    }
}

